package com.yanqu.road.logic.cross;

import com.yanqu.road.entity.rank.UnionActivityRank;
import com.yanqu.road.logic.bussiness.rank.RankBussiness;
import com.yanqu.road.logic.config.GameConfig;
import com.yanqu.road.logic.pb.RankPb;
import com.yanqu.road.logic.sort.UnionActivityRankSort;
import com.yanqu.road.logic.sort.UnionWarActivityRankSort;
import com.yanqu.road.pb.rank.UnionActivityRankProto;
import org.apache.logging.log4j.LogManager;
import org.apache.logging.log4j.Logger;

import java.util.*;

public class CrossUnionWarRankListModel {
    private static Logger logger = LogManager.getLogger(CrossUnionWarRankListModel.class.getName());

    private int rankNum = GameConfig.RANK_DEFAULT_MAX_COUNT;

    private UnionWarActivityRankSort sorter;

    private LinkedList<UnionActivityRank> rankList;

    private boolean isNeedSync = false;

    private boolean isUpdate = false;

    private int activityId;

    private int phase;

    private int groupId;

    private UnionActivityRankProto.UnionActivityRankListMsg.Builder rankListMsg;

    public void setRankNum(int rankNum) {
        this.rankNum = rankNum;
    }

    public CrossUnionWarRankListModel(int activityId, int phase, int groupId) {
        this.activityId = activityId;
        this.phase = phase;
        sorter = new UnionWarActivityRankSort();
        rankList = new LinkedList<>();
        rankListMsg = UnionActivityRankProto.UnionActivityRankListMsg.newBuilder();
        this.groupId = groupId;
    }

    public LinkedList<UnionActivityRank> getRankList() {
        return rankList;
    }

    public UnionActivityRankProto.UnionActivityRankListMsg.Builder  getRankListMsg() {
        return rankListMsg;
    }

    public void setRankList(LinkedList<UnionActivityRank> unionRankList) {
        synchronized (this) {
            rankList = new LinkedList<>(unionRankList);
            checkListValid();      //校验一下数组
            rankList.sort(sorter);
            while (rankList.size() > rankNum){
                rankList.removeLast();
            }
            initRankListMsg();
        }
    }

    /**
     * 校验数组，去掉重复数据
     */
    private void checkListValid(){
        List<Integer> needRemoveList = new ArrayList<>();
        List<String> hasUnionUidList = new ArrayList<>();
        for (int i = 0; i < rankList.size(); i++) {
            UnionActivityRank unionRank = rankList.get(i);
            if(!hasUnionUidList.contains(unionRank.getUnionUid())){
                hasUnionUidList.add(unionRank.getUnionUid());
            }else {
                needRemoveList.add(i);
            }
        }
        if(needRemoveList.size() > 0){
            Collections.sort(needRemoveList);
            Collections.reverse(needRemoveList);
            for (int index : needRemoveList) {
                rankList.remove(index);
            }
        }
    }

    private void initRankListMsg() {
        rankListMsg = RankPb.parseUnionActivityRankListMsg(rankNum, rankList);
    }

    public void removeRank(long serverId, String unionUid) {
        synchronized (this) {
            rankList.removeIf(m -> Objects.equals(m.getUnionUid(), unionUid) && m.getUnionBaseInfo().getServerId() == serverId);
            initRankListMsg();
        }
    }

    public void removeRank(String unionUid) {
        synchronized (this) {
            rankList.removeIf(m -> Objects.equals(m.getUnionUid(), unionUid));
            initRankListMsg();
            isNeedSync = true;
        }
    }

    public int getMyRank(long serverId, String unionUid) {
        int rank = -1;
        int index = 0;
        synchronized (this) {
            for(UnionActivityRank unionActivityRank : rankList){
                if(Objects.equals(unionActivityRank.getUnionUid(), unionUid)){
                    rank = index + 1;
                    break;
                }
                index++;
            }
        }
        if(rank > rankNum){
            rank = -1;
        }
        return rank;
    }

    private UnionActivityRank getUnionRankInfo(long serverId, String unionUid){
        synchronized (this) {
            for(UnionActivityRank unionActivityRank : rankList){
                if(Objects.equals(unionActivityRank.getUnionUid(), unionUid) && unionActivityRank.getUnionBaseInfo().getServerId() == serverId){
                    return unionActivityRank;
                }
            }
        }
        return null;
    }

    /**
     * 更新排行
     */
    public boolean rankChange(UnionActivityRank unionActivityRank, boolean isInit) {
        if(null == unionActivityRank){
            return false;
        }
        boolean isChange = false;
        UnionActivityRank unionRank;
        synchronized (this) {
            unionRank = getUnionRankInfo(unionActivityRank.getUnionBaseInfo().getServerId(), unionActivityRank.getUnionUid());
            if(null != unionRank){
                if (isInit) {
                    return false;
                }
                if(0 != unionRank.getValue().compareTo(unionActivityRank.getValue())){
                    unionRank.setLastUpdateTime(System.currentTimeMillis() / 1000);
                }
                unionRank.setValue(unionActivityRank.getValue());
                unionRank.setUnionBaseInfo(unionActivityRank.getUnionBaseInfo());
                isChange = true;
            }else {
                int size = rankList.size();
                if (size < rankNum) {
                    unionActivityRank.setLastUpdateTime(System.currentTimeMillis() / 1000);
                    rankList.add(unionActivityRank);
                    isChange = true;
                } else if (sorter.compare(rankList.getLast(), unionActivityRank) > 0) {
                    UnionActivityRank rank = rankList.getLast();
                    rank.setUnionUid(unionActivityRank.getUnionUid());
                    rank.setUnionBaseInfo(unionActivityRank.getUnionBaseInfo());
                    rank.setValue(unionActivityRank.getValue());
                    rank.setLastUpdateTime(System.currentTimeMillis() / 1000);
                    isChange = true;
                }
            }
            if(isChange) {
                rankList.sort(sorter);
                initRankListMsg();
                isNeedSync = true;
                isUpdate = true;
            }
        }

        return isChange;
    }

    public void saveUnionWarRankList() {
        LinkedList<UnionActivityRank> newRankList;
        synchronized (this) {
            if (!isUpdate) {
                return;
            }
            newRankList = new LinkedList<>(rankList);
            isUpdate = false;
        }
        RankBussiness.updateUnionWarRankList(activityId, phase, newRankList);
    }

    public boolean isNeedSync() {
        return isNeedSync;
    }

    public void setNeedSync(boolean needSync) {
        isNeedSync = needSync;
    }

    public boolean isUpdate() {
        return isUpdate;
    }

    public void setUpdate(boolean update) {
        isUpdate = update;
    }

    public int getActivityId() {
        return activityId;
    }

    public void setActivityId(int activityId) {
        this.activityId = activityId;
    }

    public int getPhase() {
        return phase;
    }

    public void setPhase(int phase) {
        this.phase = phase;
    }

    public int getGroupId() {
        return groupId;
    }

    public void setGroupId(int groupId) {
        this.groupId = groupId;
    }
}
